package org.intrasearch.core.io;

import java.io.IOException;
import java.io.ObjectInput;
import java.io.ObjectOutput;
import java.lang.reflect.InvocationTargetException;
import java.util.Map;

public class MapExternalizableProvider<K,V> implements ExternalizableProvider<Map<K,V>>
{
    private final Class<? extends Map> mapClass;

    public MapExternalizableProvider(Class<? extends Map> mapClass)
    {
        this.mapClass = mapClass;
    }

    public void writeExternal(Map<K, V> object, ObjectOutput output) throws IOException
    {
        output.writeInt(object.size());
        for (Map.Entry<K, V> entry : object.entrySet())
        {
            output.writeObject(entry.getKey());
            output.writeObject(entry.getValue());
        }
    }

    public Map<K, V> readExternal(ObjectInput input) throws IOException, ClassNotFoundException
    {
        Map<K, V> map = createMap();
        int size = input.readInt();
        for (int i = 0; i < size; i++)
        {
            K key = (K) input.readObject();
            V value = (V) input.readObject();
            map.put(key, value);
        }
        return map;
    }

    private Map<K, V> createMap()
    {
        try
        {
            return mapClass.getConstructor().newInstance();
        }
        catch (NoSuchMethodException e)
        {
            throw new RuntimeException(e);
        }
        catch (InvocationTargetException e)
        {
            throw new RuntimeException(e);
        }
        catch (InstantiationException e)
        {
            throw new RuntimeException(e);
        }
        catch (IllegalAccessException e)
        {
            throw new RuntimeException(e);
        }
    }
}
